<!--
    字幕与配音
-->
<script setup>
import {
  ref,
  reactive,
  toRefs,
  watch,
  onMounted,
  onUnmounted,
  nextTick,
  computed,
  provide,
  h,
  createVNode,
  watchEffect,
} from "vue";

import utils from "@/common/utils/utils.js";

import dayjs from "dayjs";
// 富文本
import TextEditing from "./Component/TextEditing.vue";
// import TextEditing from "@/views/shotstack/MuseMixedCut/mixedCutCreat/components/Component/TextEditing.vue";

// 文案库组件
import CopyLibraryModal from "@/components/AddTextModal/CopyLibraryModal.vue";
const copyLibraryModal = ref(null);

// 文案仿写
import TextImitationDialog from "@/views/shotstack/components/TextImitationDialog/index.vue";
const TextImitationDialogRef = ref(null);

// 充值弹窗
import vipModal from '@/socialMedia/Vip/vipModal.vue'
const vipModalRef = ref(null)

// loading 遮罩
import loadingMask from '@/components/loadingMask/index.vue'
const loadingMaskRef = ref()

// icon
import {
  CloseOutlined,
  DeleteOutlined,
  PlusOutlined,
  UploadOutlined,
  LoadingOutlined,
  PauseOutlined,
  CaretRightOutlined,
  ExclamationCircleOutlined,
  FileDoneOutlined,
  InfoCircleOutlined
} from "@ant-design/icons-vue";
import {
  calculateDraggableArea,
  measureTextWithSpan,
  getTextWidthUsingCanvas,
  baseTts_config,
  sizeData,
  resetXY,
  hexToRgba,
  subtitleHeightratio,
  xLocation,
} from "../../utools/index.js";

// 处理配置应用到全部字幕组
import {
  // 应用所有字幕配置
  applyallSubtitle,
  // 应用所有音频配置(会重新获取音频)
  applyallVoice,
  importListToRichtext_subtitle,
  // 视频截取首帧画面
  captureFirstFrame,
  // 判断视频组是否有文字和音频
  hasText,
  hasVideo,
  chunkArray,
  chunkNum
} from "@/common/utils/richTextProcessing.js";

// 提示框
import { Modal } from "ant-design-vue";

// 全局轻提示
import { message } from "ant-design-vue";

import request from "@/common/utils/request";

// 音频上传可视化组件
import ViewAudioModel from "@/views/shotstack/MuseMixedCut/mixedCutCreat/components/Component/ViewAudioModel.vue";

// 仓库
import { useStore } from "vuex";
const store = useStore();

// 路由
import { useRoute, useRouter } from "vue-router";
const route = useRoute();
// const router = useRouter();

// 字幕与配音组件
import SubtitlesFontStyleComponent from "./SubtitlesFontStyleComponent.vue";
// 手机组件
import { DraggableContainer } from "vue3-draggable-resizable";

import Vue3DraggableResizable from "vue3-draggable-resizable";
//default styles
import "vue3-draggable-resizable/dist/Vue3DraggableResizable.css";
import { nanoid } from "nanoid";

import {getText_to_speechConfig} from '@/common/utils/atherUtils.js'
// 获取特效数据
import {getSubtitleEffect_config} from '@/views/shotstack/MixedCutPlatforms/utools/template.js'


let state = ref([]);
// store.commit('videoMixCut/INIT_SUBTITLES_DATA', subTitle.value)

const emit = defineEmits(["openUpLoad:type"]);

const tips = ref('')

// 仓库中的混剪数据
const VideoMashup = computed(() => {
  return store.state.videoMixCut.VideoMashup;
});

// 仓库中的克隆字幕数据
const subTitle = computed(() => {
  return store.state.videoMixCut.Subtitles;
});

// 充值弹窗开关
const vipVisible = ref(false)

// 模板广场页面带过来的 id
const queryData = computed(() => {
  return {
    viewType: route.query?.viewType, // 1模板详情, 2混剪详情
    id: route.query?.id, // 详情id
    key: route.query?.key, // 获取详情的id键名
    type: route.query?.type, // 用于区分新建的类型
    templateType: route.query?.templateType, // 用于区分查看模板详情的类型 1为我的模板 2为模板广场
    createType: route.query?.createType, // 用于区分模板创建类型 1为网络连接 2为素材库 3为手动创建
    useType: route.query?.useType, // 用于区分模板使用的类型 edit 编辑 view 详情 use使用
    typeofuse: route.query?.typeofuse, // 用于区分模板点击使用使用的类型 myTemplate为我的模板 squareTemplate为模板广场
    openType: route.query?.openType, // 用于区分模板点击使用使用的类型 myTemplate为我的模板 squareTemplate为模板广场
  };
});

// 背景设置的参数
const bgc = computed(() => {
  const data = store.state.videoMixCut.VideoMashup.background
  if (data?.type == 1) {
    return {
      'background': data.rgba
    }
  } else if (data?.type == 2 || data?.type == 3) {
    let url = data.material_urls[0].url
    return {
      'background': `url(${url})`,
      'background-position': 'center',
      'background-size': 'cover'
    }
  } else {
    return {
      'background': '#707070'
    }
  }
});

// 获得字体大小转换的比例
const scaleData = computed(() => {
  const { showHeight, showWidth } = store.state.videoMixCut.VideoMashup;
  return resetXY(showHeight, showWidth);
});

// 当前预览的下标
const currentDrawerIndex = computed({
  get() {
    return store.state.videoMixCut.currentIndex;
  },
  set(val) {
    store.commit("videoMixCut/CHANGE_CURRENT_INDEX", val);
  },
});

// 当前编辑字幕的类型
const tab_id = computed(() => {
  return subTitle.value[currentDrawerIndex.value.index].tab_id;
});

// 当前展开的字幕项
const currentId = computed({
  get() {
    return store.state.videoMixCut?.current_tts_id || "";
  },
  set(val) {
    store.commit("videoMixCut/MODIFY_TTS_ID", val);
  },
});

// 分开字幕与配音的数据
const dataSeparation = computed(() => {
  const obj = {
    tts_config_text: [],
    tts_config_audio: [],
  };
  if (subTitle.value.length) {
    // debugger
    const target = subTitle.value[currentDrawerIndex.value.index];
    target.tts_config.forEach((ele) => {
      if (ele.tab_id == "text") {
        obj.tts_config_text.push(ele);
      } else {
        obj.tts_config_audio.push(ele);
      }
    });
  }
  return obj;
});

/**
 * 当前富文本编辑项的内容
 * @param { text: 前编辑项(subtitle)的文本, id: 当前编辑项(subtitle)的id }
 */
const editSubtitleData = computed(() => {
  return store.state.videoMixCut.editSubtitleData;
});

const spanWidth = ref(0);

const editSubtitleMsg = computed(() => {
  return subTitle.value[currentDrawerIndex.value.index].tts_config
    .find((ele) => ele.tts_id == currentId.value)
    ?.subtitle.find((i) => i.subtitle_id == editSubtitleData.value.id);
});

// 当前正在编辑的 subtitle项
const targetSubtitle = computed(() => {
  let subtitle = null;
  let targettTS = subTitle.value[currentDrawerIndex.value.index].tts_config.find(
    (ele) => ele.tts_id == currentId.value
  );
  subtitle = targettTS?.subtitle.find(
    (item) => item.subtitle_id == editSubtitleData.value.id
  );
  // || targettTS?.subtitle?.[0];
  return subtitle || targettTS?.subtitle?.[0]
  // return subtitle || targettTS?.subtitle?.[0]
  // return subtitle || targettTS?.subtitle?.[0];
});

// 获取当前编辑的项 和其位置信息
const editSubtitleItem = computed({
  get() {
    if (!!targetSubtitle.value) {
      // console.log("find的值----------------", find.x, find.text);
      const { x, y, text, subtitle_id } = targetSubtitle.value;
      return { x, y, text, subtitle_id };
    } else {
      return {
        x: 0,
        y: 0,
        text: "",
        subtitle_id: Math.random().toString(36).slice(2, 10),
      };
    }
  },
});
// 控制手机显示隐藏
const phoneVisible = ref(false);
const props = defineProps({
  title: {
    type: String,
    default: "",
  },
});

// 字体组件
const Subtitles_FontStyleComponent = ref(null);

const lineMsg = ref({
  parentindex: null, // 父项索引
  parentid: null, // 父项id
  itemid: null, // 编辑项id
  itemindex: null, // 编辑项下标
  startOffset: null, // 当前光标的位置
  data: null, // 当前光标位置的文本数据
});
// 实时获取光标的位置和正在编辑的元素


// 修改当前的展开项
const foldManual = (id) => {
  currentId.value = id;
};
// 添加字幕项
const addeditorArr = () => {
  const pushItem = JSON.parse(
    JSON.stringify(dataSeparation.value.tts_config_text[0])
  );
  // const pushItem = baseTts_config()
  pushItem.tab_id = "text";
  const id = nanoid();
  pushItem.tts_id = id;
  const pushSubtitle = JSON.parse(
    JSON.stringify(dataSeparation.value.tts_config_text[0]?.subtitle[0])
  );
  pushSubtitle.subtitle_id = nanoid();
  pushSubtitle.text = "";
  pushSubtitle.ssml = "<speak></speak>";
  pushSubtitle.start_time = 0;
  pushSubtitle.end_time = 0;
  pushSubtitle.audio_url = "";
  pushSubtitle.duration = 0;

  pushItem.subtitle = [pushSubtitle];
  pushItem.ssmlContent = `<speak subid="${pushSubtitle.subtitle_id}" tts_id="${id}"></speak>`;
  pushItem.subtitle_effects = getSubtitleEffect_config()
  subTitle.value[currentDrawerIndex.value.index].tts_config.push(pushItem);
  // debugger
  store.commit("videoMixCut/INIT_SUBTITLES_DATA", subTitle.value);
  nextTick(() => {
    currentId.value = id;
    // currentId.value = dataSeparation.value.tts_config_text[dataSeparation.value.tts_config_text.length - 1].tts_id
    console.log(dataSeparation.value, "dataSeparation");
  });
};

// 音频播放节点
const globalAudio = ref(null);
// 是否正在播放
const isPlaying = ref(false);
// 哪一项在播放 (存放的是url)
const playingItem = ref(null);

// 播放完毕
const handleGlobalAudioEnded = () => {
  globalAudio.value.currentTime = 0;
  isPlaying.value = false;
};

// 切换字幕生成方式
const switchDisplay = (type) => {
  // debugger
  store.commit("videoMixCut/CHANGE_TTS_TAB_ID", type);
  // 设置当前编辑的项为 第一项
  lineMsg.value.parentindex = 0;
  if (type == "text") {
    currentId.value = dataSeparation.value.tts_config_text[0].tts_id;
  } else {
    currentId.value = dataSeparation.value.tts_config_audio[0].tts_id;
  }
};

// 获取当前选中的弹幕
const resizableStyle = computed(() => {
  const sizeData = calculateDraggableArea(
    +distinguishability.value.width,
    +distinguishability.value.height
  );
  console.log(background.value, "背景");
  return {
    width: sizeData.draggableWidth + "px",
    height: sizeData.draggableHeight + "px",
    transition: "all 0.3s",
    'z-index': 1,
    background: 'transparent'
  };
});

const parentBgc = computed(() => {
  let returnVal =
    background.value.type == "color"
      ? {
        background: background.value.url,
      }
      : {
        background: `url(${background.value.url})`,
        'background-repeat': 'no-repeat',
        'background-size': 'contain',
        "backgroundPosition": "center",
      };

  return returnVal
})

/**
 * 手机相关逻辑
 */
// 文字外边框的宽高
const ResizableWidth = ref("100%");
const Resizableheight = ref("100%");

// 当前使用的字体样式

// 计算字体样式
const coverStyle = computed(() => {
  return function () {
    let tergetItem =
      subTitle.value?.[currentDrawerIndex.value.index].tab_id == "audio"
        ? dataSeparation.value.tts_config_audio[0].subtitle[0]
        : dataSeparation.value.tts_config_text[0].subtitle[0];
    // console.log(tergetItem);
    nextTick(() => {
      // let isDom = document.getElementById("editor_content_p");
      // const rect = isDom?.getBoundingClientRect();
      let domObj = document.getElementById("editor_content_p");
      // 复制一个元素, 计算宽度
      const width = measureTextWithSpan(domObj, domObj.textContent).width;
      ResizableWidth.value = width;
      Resizableheight.value = domObj?.offsetHeight;
    });
    // });
    if (tergetItem) {
      // 计算字体的显示比例
      const size = tergetItem.font_size;
      const width = VideoMashup.value.showWidth;
      const height = VideoMashup.value.showHeight;
      // 获取当前缩放的比例
      const { scaleWidth } = resetXY(height, width);
      // 使最后的结果再大一些
      // const font_size = size / scaleWidth
      const font_size = size / scaleWidth;
      let flower_style;
      // 获取花字的对应样式
      // 获取文字阴影
      const shadow = () => {
        let { borderw, bordercolor } = tergetItem?.preset_styles_config;
        borderw = borderw / 3;
        if (borderw && bordercolor) {
          const shadows = [];
          for (let x = -borderw; x <= borderw; x++) {
            for (let y = -borderw; y <= borderw; y++) {
              if (x !== 0 || y !== 0) {
                shadows.push(`${x}px ${y}px 0 ${bordercolor}`);
              }
            }
          }
          return shadows.join(",");
        } else {
          return "";
        }
      };
      flower_style = {
        // 字体颜色
        color: tergetItem.preset_styles_config.fontcolor || tergetItem.color,
        // 字体描边颜色以及宽度
        // 背景色
        // 'background-color': tergetItem.preset_styles_config.boxcolor,
        // 转换背景色和透明度
        "background-color": hexToRgba(
          tergetItem?.preset_styles_config.boxcolor,
          tergetItem?.preset_styles_config.box_color_alpha
        ),
        // 边框的粗细
        padding: `${tergetItem?.preset_styles_config?.boxborderw
          ? tergetItem?.preset_styles_config?.boxborderw / 4
          : 0
          }px`,
        "border-radius": tergetItem?.preset_styles_config.boxradius / 3 + "px",
        // padding: `${tergetItem.preset_styles_config.boxborderw / 4}px`,
        // 文字阴影
        "text-shadow": shadow(),
      };

      const reTurnData = {
        cursor: "grab",
        "font-family": tergetItem.font_family,
        "font-size": font_size + "px",
        color: tergetItem.color,
        "background-color": tergetItem.bg_color,
        textAlign:
          tergetItem.alignment == "left"
            ? "left"
            : tergetItem.alignment == "right"
              ? "right"
              : "center",
        fontWeight: tergetItem.bold == 1 ? "bold" : "normal",
        fontStyle: tergetItem.italic == 1 ? "italic" : "normal",
      };
      if (!!flower_style) {
        return {
          ...reTurnData,
          ...flower_style,
        };
      } else {
        return reTurnData;
      }
    } else {
      return {};
    }
  };
});

const showImg = ref(true);

const coverForm = ref({
  cover_duration: 0.05,
  poster_url: "",
});

// 分辨率
const distinguishability = ref({
  width: "",
  height: "",
});
const ResizableActive = ref(false);

// 拖动结束修改 x和y的位置
const dragEndHandle = (data) => {
  // return;
  console.log("拖拽结束", data);
  // nextTick(() => {
  const spanDom = document.getElementById("editor_content_p");
  spanWidth.value = spanDom?.offsetWidth;
  console.log("修改位置调用", data, spanWidth.value, data.x + spanWidth.value / 2);
  store.commit("videoMixCut/MODIFY_SUBTITLES_POSITION", {
    x: data.x,
    y: data.y,
    showX: (data.x + spanWidth.value / 2) + 1.5,
    rightX: data.x + spanWidth.value,
    id: editSubtitleData.value.id,
  });
};

// 切换镜头组
const prevGroup = (type) => {
  // 上一个
  if (type == "last") {
    if (currentDrawerIndex.value.index > 0) {
      currentDrawerIndex.value.index = currentDrawerIndex.value.index - 1;
      currentId.value =
        VideoMashup.value.resource_data[
          currentDrawerIndex.value.index
        ].tts_config[0].tts_id;
      title_top.value =
        VideoMashup.value.resource_data[currentDrawerIndex.value.index].name;
    }
  } else if (type == "next") {
    // 下一个
    if (currentDrawerIndex.value.index < subTitle.value.length - 1) {
      currentDrawerIndex.value.index = currentDrawerIndex.value.index + 1;
      title_top.value =
        VideoMashup.value.resource_data[currentDrawerIndex.value.index].name;
      currentId.value =
        VideoMashup.value.resource_data[
          currentDrawerIndex.value.index
        ].tts_config[0].tts_id;
    }
  }

  useBgc();
};

const audio_name = ref("");

// 选择音频素材回调
const getVoiceData = (data, type) => {
  console.log(data, "选择的素材");
  if (data && data.material_size_text !== "") {
    // 替换
    if (type == "replay") {
      const index = start_upload_Alldata.value.findIndex(
        (ele) => ele.id == start_upload_data.value.id
      );
      if (index != -1) {
        start_upload_Alldata.value[index] = {
          id: data.id,
          url: data.material_url, // 音频路径
          name: data.material_name, // 音频名字
          isOK: true, // 是否转码 成功
          material_duration: data.material_duration,
          media_id: data?.oss_media_id || "",
        };
      } else {
        start_upload_Alldata.value.push({
          id: data.id,
          url: data.material_url, // 音频路径
          name: data.material_name, // 音频名字
          isOK: true, // 是否转码 成功
          material_duration: data.material_duration,
          media_id: data?.oss_media_id || "",
        });
      }
      // 修改传递给弹窗的值
      start_upload_data.value = {
        name: data.material_name,
        id: data.id,
        url: data.material_url, // 音频路径
        name: data.material_name, // 音频名字
        material_duration: data.material_duration,
        media_id: data?.oss_media_id || "",
      };

      nextTick(() => {
        audioDialog.value &&
          audioDialog.value.initCanvasFn(start_upload_data.value);
      });
    } else {
      start_upload_Alldata.value.push({
        id: data.id,
        url: data.material_url, // 音频路径
        name: data.material_name, // 音频名字
        isOK: true, // 是否转码 成功
        material_duration: data.material_duration,
        media_id: data?.oss_media_id || "",
      });
    }
    audio_name.value = data.material_name;
    console.log(start_upload_data.value, "修改传送给子组件的值");
  }
};
// 控制抽屉显示
const visible = ref(false);

watch(
  () => visible.value,
  (nv) => {
    // 清空当前试听的状态
    store.commit("videoMixCut/SETVIDEOPLAYING_DATA", {
      isPlay: false,
      audio_url: "",
      reset: false, // 是否从头播放
      changeUrl: false, // 是否修改url
    });
  }
);

const title_top = ref("");

// 宽度侦听器
const resizeObserver = ref(null);

// 打开抽屉的 - 获取正在操作项的项
const openDrawer = async (index) => {

  try {
    tips.value = await getText_to_speechConfig()
  } catch (error) {
  }

  // 侦听手机组件 span的宽度, 动态设置该项数据的x和y
  resizeObserver.value = new ResizeObserver((entries) => {
    for (let entry of entries) {
      const computedStyle = getComputedStyle(entry.target);
      // 计算包含 padding 的宽度
      const paddingLeft = parseFloat(computedStyle.paddingLeft);
      const paddingRight = parseFloat(computedStyle.paddingRight);
      const totalWidth = entry.contentRect.width + paddingLeft + paddingRight;
      spanWidth.value = totalWidth;
      ResizableWidth.value = totalWidth
      // let target = subTitle.value[currentDrawerIndex.value.index].tts_config
      //   .find((ele) => ele.tts_id == currentId.value)
      //   ?.subtitle.find(
      //     (item) => item.subtitle_id == editSubtitleData.value.id
      // );
      const target = subTitle.value[currentDrawerIndex.value.index]?.tts_config
        .find((ele) => ele.tts_id == currentId.value)
        ?.subtitle.find((i) => i.subtitle_id == editSubtitleData.value.id);
      console.log(target, '找到的项---------------------------');

      // return;
      !!target &&
        (() => {
          // const x = target.showX - spanWidth.value / 2 >= 0
          //   ? target.showX - spanWidth.value / 2
          //   : 0;
          const x = target.showX - spanWidth.value / 2
          const rightX = target.showX + spanWidth.value / 2
          console.log(x, "更新位置");
          store.commit("videoMixCut/MODIFY_SUBTITLES_POSITION", {
            x: x < 0 ? 0 : x,
            y: target.y,
            rightX,
            showX: target.showX,
            spanWidth: spanWidth.value,
            id: editSubtitleData.value.id,
          });
          console.log('修改的值----------------', target.showX - spanWidth.value / 2);


        })();
    }
  });
  currentDrawerIndex.value = index;

  useBgc();

  // 克隆数据, 用于修改 最后保存
  store.commit(
    "videoMixCut/INIT_SUBTITLES_DATA",
    JSON.parse(JSON.stringify([...VideoMashup.value.resource_data]))
  );
  title_top.value =
    VideoMashup.value.resource_data[currentDrawerIndex.value.index].name;

  store.commit("videoMixCut/MODIFY_TTS_ID", subTitle.value);
  // 存储当前编辑的下标
  store.commit(
    "videoMixCut/CHANGE_CURRENT_INDEX",
    JSON.parse(JSON.stringify(index))
  );
  nextTick(() => {
    if (tab_id.value == "text") {
      const id = VideoMashup.value.resource_data[currentDrawerIndex.value.index].tts_config.find(ele => ele.tab_id == "text")?.tts_id
      currentId.value = id
    } else {
      const id = VideoMashup.value.resource_data[currentDrawerIndex.value.index].tts_config.find(ele => ele.tab_id == "audio")?.tts_id
      currentId.value = id
    }
    console.log(currentId.value, "currentId.value");
    // 侦听 span 的宽度
    nextTick(() => {
      resizeObserver.value.observe(document.getElementById("editor_content_p"));
    })
  });
  // 存储当前的分辨率
  distinguishability.value.width = VideoMashup.value.width;
  distinguishability.value.height = VideoMashup.value.height;
  visible.value = true;


  // 获取字体数据 + 手机状态数据回显
  // getFontClass();
  setTimeout(() => {
    phoneVisible.value = true;
  }, 550);
};

const background = ref({
  type: "color",
  url: "transparent",
});
// 使用的背景
const useBgc = async () => {
  // 判断使用的背景
  const material =
    VideoMashup.value.resource_data?.[currentDrawerIndex.value.index]
      .material_list?.[0];

  if (material?.scene_type == "video") {
    const url = await captureFirstFrame(material.material_url);
    
    if (url) {
      background.value = { url, type: "img" };
    } else {
      // background.value = "transparent";
      background.value = { url: "transparent", type: "color" };
    }
  } else if (material?.scene_type == "image") {
    const url = material.material_url;
    url
      ? (background.value = { url, type: "img" })
      : (background.value = { url: "transparent", type: "color" });
  } else {
    background.value = { url: "transparent", type: "color" };
  }
};

const submitLoading = ref(false)
// 点击确定保存数据
const submitConfirm = async () => {
  // 判断最后是否关闭弹窗
  let isClose = ref(true);
  let isNotEmpty = false;
  console.log(subTitle.value, "subTitle.value");

  // 开启遮罩
  loadingText.value = "音频获取中..."
  loadingFlage.value = true


  if (tab_id.value == "text") {
    // 检查是否有空的项 false 有空项 true 无空项
    // 只有当字幕组有多项时检验是否有空, 或者只有一项 但是subtitle有多项时检验
    if (dataSeparation.value.tts_config_text.length > 1) {
      const textEmpty = dataSeparation.value.tts_config_text.every((ele) => {
        return ele.subtitle.every(
          (i) => !!i.text.trim() && i.text.trim() !== "\n"
        );
      });
      if (!textEmpty) {
        loadingFlage.value = false
        return message.warning("字幕组中存在空项,请填写或删除后再保存");
      }
    } else {
      if (dataSeparation.value.tts_config_text[0].subtitle.length > 1) {
        const textEmpty = dataSeparation.value.tts_config_text[0].subtitle.every((ele) => {
          return !!ele.text.trim() && ele.text.trim() !== "\n"
          // return ele.subtitle.every(
          // );
          // return ele.subtitle.every(
          //   (i) => !!i.text.trim() && i.text.trim() !== "\n"
          // );
        });
        if (!textEmpty) {          
          loadingFlage.value = false
          return message.warning("字幕组中存在空项,请填写或删除后再保存");
        }
      }
    }

    // 文本需要检测是否开启音频
    isNotEmpty = dataSeparation.value.tts_config_text.some((ele) => {
      return (
        ele.subtitle.some((i) => !!i.text.trim() && i.text.trim() !== "\n") &&
        ele.showVoice
      );
    });
    // 必须要有文字
    // const haveText = dataSeparation.value.tts_config_text.every((ele) => {
    //   return ele.subtitle.every(ele => ele.text && ele.text.trim() != "\n")
    // })
    // 每一项是否都开启了音频
    // const openVoice = dataSeparation.value.tts_config_text.every((ele) => {
    //   return ele.showVoice
    // });


    // 是否开启音频
    const type =
      subTitle.value[currentDrawerIndex.value.index].time_strategy.type;
    // 存在没有音频的项  并且开启了配音, 并且是随音频 => 获取每一项的音频
    if (isNotEmpty) {
      // if (isNotEmpty && type != 0 && type != 3) {
      // 只取没有音频的项, 获取音频

      // 只取没有音频的项, 获取音频
      const textAndSubtitleId = dataSeparation.value.tts_config_text.flatMap(
        (ele) =>
          ele.subtitle
            .filter(
              (sub) =>
                !!sub.text.trim() && sub.text.trim() !== "\n" && !sub.audio_url
            )
            .map((sub) => ({ text: sub.ssml, id: sub.subtitle_id }))
      );

      
      const allText = dataSeparation.value.tts_config_text.flatMap(
        (ele) =>
        ele.subtitle
        .filter(
              (sub) =>
              !!sub.text.trim() && sub.text.trim() !== "\n" && !sub.audio_url
            )
            .map((sub) => sub.text)).join('')
            
      console.log(allText,'所有要请求的数据');

      // 提示积分消耗
      const number = allText.length
      try {
        const res = await utils.textConfigGet({
          number
        })
        // 查询积分, 积分不足则走不到这一步
        // 获取积分消耗提示内容
        // const content = utils.useText(res)
        // try {
        //   // 确认消耗
        //   await utils.kd({ content,res })
        // } catch (error) {
        //   return
        // }
      } catch (error) {
        // 打开充值, 接着打开点数购买
        vipVisible.value = true
          vipModalRef.value && vipModalRef.value.openBuyVisible()
        return
      }
      

      const getTTsVoice = async () => {
        return new Promise(async (resolve, reject) => {
          submitLoading.value = true;
          message.loading("字幕语音转换中...", 0);

          try {
            // 异步数组
            let promiseList = []

            // 每一个异步函数

            const promiseItem = (data) => {
              const { requestData } = data
              return new Promise(async (resolve, reject) => {
                // 获取此项 tts的音频选项
                console.log(requestData, '每一组的每一个接受到的参数');
                try {
                  const res = await request.post(
                    "/work_ai",
                    "/user/shotstack/textToVoice/many",
                    { ...requestData, mexid_all: false }
                  );
                  console.log(res.result, "many调用的结果");

                  // 创建一个函数用于延迟
                  const delay = (ms) => new Promise((resolve) => setTimeout(resolve, ms));

                  // 找到对应的数据, 存放数据
                  const setVoice = (arr) => {
                    dataSeparation.value.tts_config_text.flatMap((sub, index) => {
                      sub.subtitle.forEach((ele) => {
                        const findTarget = arr.find((i) => i.id == ele.subtitle_id);
                        if (!!findTarget) {
                          ele.audio_url = findTarget.audio;
                          ele.duration = +findTarget.duration * 1000;
                          if(findTarget?.duration_ms && findTarget?.duration_ms > 0){
                            ele.duration = +findTarget.duration_ms;
                          } 
                          ele.end_time = +ele.duration;
                          ele.media_id = findTarget?.oss_media_id || "";
                          ele.material_path = findTarget?.material_path || "";
                        }
                      });
                    });
                  };

                  // 使用新的获取音频接口
                  const getItemVoice = async () => {
                    const itemVoice = await request.get(
                      "/work_ai",
                      `/user/shotstack/textToVoice/many/result/${requestData.unique}`
                    );
                    console.log("单项的轮询结果123", itemVoice);
                    if (itemVoice?.code && itemVoice?.code != 1000) {
                      throw new Error(itemVoice);
                    }
                    if (itemVoice?.result?.status) {
                      if (itemVoice.result.status == "loading") {
                        await delay(2000);
                        await getItemVoice();
                        return;
                      }
                      if (itemVoice.result.status == "error") {
                        return message.error("音频获取失败!");
                      }
                    } else {
                      console.log("itemVoice?.result 有数据啦", itemVoice?.result);
                      setVoice(itemVoice?.result);
                    }
                  };
                  await getItemVoice();
                } catch (error) {
                  message.destroy();
                  isClose.value = false;
                  submitLoading.value = false;
                  nextTick(() => {
                    message.error("字幕语音转换失败,请重试!");
                  });
                  reject()
                }
                // 轮询结束了
                resolve()
              })
            }

            // 循环中 处理每一组数据, 将subtitle 扁平数组 处理成 嵌套数组 每一个嵌套数组处理成一个请求项
            const subChunkArr = chunkArray(textAndSubtitleId, chunkNum)

            for (let ele of subChunkArr) {

              const { speed, tone_id, volume, voice_type, recommendSpeed, emotion_category, emotion_intensity, id,
                category } =
                dataSeparation.value.tts_config_text[0];

              const requestData = {
                text: ele,
                // 火山的音色 用火山的语速
                speed: voice_type == 2 ? recommendSpeed : speed,
                timbre_id: tone_id,
                volume,
                emotion_category,
                emotion_intensity,
                unique: nanoid(),
                id,
                category
                // ssml_content
              };
              // 参数传入到异步函数中
              promiseList.push(() => promiseItem({
                requestData
              }))
            }

            // return

            // 将所有的请求项处理为 分组函数
            const promiseGrouping = chunkArray(promiseList, chunkNum)

            for (let i = 0; i < promiseGrouping.length; i++) {
              await Promise.all(promiseGrouping[i].map(i => i())).then(res => {
                console.log('一组成功');
              }).catch(err => {
                console.log(err, '一组失败');
              })
            }

            // 有音频,  配置的时长设置为随音频 修改为 => 第一个字幕组的音频时长
            if (type != 0 && type != 3) {
              // 从此视频组中 找到不为空的第一项 修改素材的时长为第一个有内容的字幕组的音频时长
              let time = 0
              let targetConfig = dataSeparation.value.tts_config_text.find((ele) =>
                ele.subtitle.some((i) => !!i.text.trim() && i.text.trim() !== "\n")
              );
              // targetConfig.subtitle.forEach((ele) => {
              //   time += ele.duration;
              // });
              time = +targetConfig.duration
              console.log(time, "素材的时长");
              subTitle.value[currentDrawerIndex.value.index]?.material_list.forEach(
                (ele) => {
                  if (type == 1) {
                    // 1 为自动变速
                    if (ele.scene_type == "image") {
                      ele.end_time = time;
                    } else {
                      ele.end_time = time;
                    }
                  } else {
                    // 2 为智能截取
                    if (ele.scene_type == "image") {
                      ele.end_time = time;
                    } else {
                      if (ele.material_duration >= +time) {
                        ele.end_time = time;
                      } else {
                        ele.end_time = +ele.material_duration;
                      }
                    }
                  }
                }
              );
            }

            console.log(dataSeparation.value.tts_config_text, "处理完成");
            resolve()
          } catch (error) {
            message.destroy();
            isClose.value = false;
            submitLoading.value = false;
            nextTick(() => {
              message.error("字幕语音转换失败,请重试!");
            });
            reject()
          }

        })
      }

      await getTTsVoice()

    } else {
      // 没有值 或关闭配音 => 修改时间设置为视频原始时长
      subTitle.value[currentDrawerIndex.value.index].time_strategy.type = 0;
      // 修改素材的结束时间为原视频时长
      subTitle.value[currentDrawerIndex.value.index].material_list.forEach(
        (item) => {
          item.end_time = +item.material_duration;
        }
      );
    }
  } else if (tab_id.value == "audio") {
    console.log(
      dataSeparation.value.tts_config_audio,
      "dataSeparation.value.tts_config_audio"
    );
    // true为有音频 false 为没有音频
    isNotEmpty = dataSeparation.value.tts_config_audio.some((ele) => {
      return !!ele.audio_url && ele.duration;
    });

    console.log(isNotEmpty, "是否有音频");
    const type =
      subTitle.value[currentDrawerIndex.value.index].time_strategy.type;
    // 没有音频, 并且当前项的时长设置为 随音频 => 修改为 视频原始时长
    if (!isNotEmpty && type != 0 && type != 3) {
      subTitle.value[currentDrawerIndex.value.index].time_strategy.type = 0;
      // 修改素材的结束时间为原视频时长
      subTitle.value[currentDrawerIndex.value.index].material_list.forEach(
        (item) => {
          item.end_time = +item.material_duration;
        }
      );
    } else if (isNotEmpty && type != 0 && type != 3) {
      // 有音频, 并且视频组设置为随音频 => 修改素材为 音频的时长
      subTitle.value[currentDrawerIndex.value.index].material_list.forEach(
        (item) => {
          item.end_time =
            +dataSeparation.value.tts_config_audio[0].duration.toFixed(0);
        }
      );
    }
    // store.dispatch("videoMixCut/SetVideoMashupItem", {
    //   key: "resource_data",
    //   value: [...subTitle.value],
    // });
  }

  // 父项 添加总时长
  dataSeparation.value.tts_config_text.forEach((ele) => {
    if (ele.subtitle.length) {
      const allTime = ele.subtitle.reduce(
        (all, item) => +all + +item.duration,
        0
      );
      const ssml = ele.subtitle.map((i) => i.ssml).join("")
      console.log(ssml,'ssmlContent');
      
      // ele.ssmlContent = ssml;
      ele.duration = +allTime;
    }
  });

  message.destroy();
  submitLoading.value = false;
  loadingFlage.value = false
  if (isClose.value) {

    const targetData = subTitle.value[currentDrawerIndex.value.index];
    // 是否有文字
    const isNotEmpty = ref(hasText({
      targetData
    }))
    // 判断是否有音频
    const isNotEmptyVideo = hasVideo({
      isNotEmpty,
      VideoMashup,
      targetData
    })
    // 如果有音频, 并且没有使用全局音频 则将此项变为随音频
    if (!isNotEmptyVideo.disabled && VideoMashup.value.global_tts_config.type != 1) {
      subTitle.value[currentDrawerIndex.value.index].time_strategy.type = 2

    // 同步修改 素材的时长
    const text_tts_configs = subTitle.value[currentDrawerIndex.value.index].tts_config.filter((item) => item.tab_id == "text");
    const haveVideo = text_tts_configs.some((ele) =>
                ele.subtitle.some((i) => !i.audio_url)
    );

    if (!haveVideo) {
      const allTextTime = text_tts_configs.reduce((totalDuration, item) => {
              // 计算当前 item 中 subtitle 所有 duration 的总和
              const currentItemDuration = item.subtitle.reduce((prev, next) => prev + +next.duration, 0);
              // 将当前 item 的总 duration 累加到总时长中
              return totalDuration + currentItemDuration;
          }, 0);
              const end_time = allTextTime.toFixed(0);

                // 如果是智能截取 =>
                subTitle.value[currentDrawerIndex.value.index].material_list.forEach((item) => {
                  if (item.scene_type == "image") {
                    item.end_time = +end_time;
                  } else {
                    if (end_time <= item.material_duration) {
                      item.end_time = +end_time;
                    } else {
                      item.end_time = +item.material_duration;
                    }
                  }
                });
    }
    }
    store.dispatch("videoMixCut/SetVideoMashupItem", {
      key: "resource_data",
      value: [...subTitle.value],
    });



    console.log(VideoMashup.value, "提交改变后的数据");
    closeDrawer();
  }
};

// 关闭抽屉的方法
const closeDrawer = () => {
  resizeObserver.value.unobserve(document.getElementById("editor_content_p"));
  visible.value = false;
  phoneVisible.value = false;
};

watch(
  () => visible.value,
  (nv) => {
    if (!nv) {
      visible.value = false;
      phoneVisible.value = false;
      start_upload_Alldata.value = [];
    }
  }
);

const close = () => {
  Modal.confirm({
    title: "温馨提示",
    icon: createVNode(ExclamationCircleOutlined),
    content: "当前未保存，是否退出设置，退出后将不会保存这次编辑",
    cancelText: "取消",
    okText: "确认",
    onOk() {
      closeDrawer();
    },
    onCancel() {
      // console.log('Cancel');
    },
    class: "test",
  });
};

// 配置应用到全部
const addVideoGroupHandle = () => {
  // 基础数据, 用于替换其他视频组的数据
  Modal.confirm({
    title: "提示",
    icon: createVNode(ExclamationCircleOutlined),
    content: "是否将字幕设置应用到全部镜头组？",
    okText: "确认",
    cancelText: "取消",
    class: "test",
    onOk() {
      // try {
      // 使用不同的数据做基础数据
      applyallSubtitleFn()
    },
    onCancel() {
      // console.log('Cancel');
    },
  });
};

// 配音应用到全部
const configurationOverride = () => {
  Modal.confirm({
    title: "提示",
    icon: createVNode(ExclamationCircleOutlined),
    content: "是否将配音设置应用到全部镜头组？注意，如果配音参数不一致，会重新生成新的音频",
    okText: "确认",
    cancelText: "取消",
    class: "test",
    onOk() {
      // try {
      // 使用不同的数据做基础数据
      useConfigurationOverrideFn()
    },
    onCancel() {
      // console.log('Cancel');
    },
  });
}

/**
 * 音频模块逻辑
 */

const start_upload_Alldata = ref([]);
// 打开预览 音频 弹窗  做音频的裁剪
const audioDialog = ref(null);
const start_upload_data = ref({});
const toAudio = (data) => {
  start_upload_data.value.name = data.name;
  start_upload_data.value.url = data.url;
  start_upload_data.value.id = data.id;
  start_upload_data.value.material_duration = data.material_duration;
  start_upload_data.value.media_id = data.media_id || "";
  audioDialog.value && audioDialog.value.showModal(data);
};
// 获取音频识别数据
const update = (data) => {
  initData(data);
};

// 关闭弹窗, 取消轮询
const cancelLoding = () => {
  timerId.value && clearTimeout(timerId.value);
};

// 带着id 轮训音频拆分的结果
const timerId = ref(null);
const closeedLoading = ref(false);
// 音频字幕的数据  获取及处理  放进 configes_audio
const initData = async (data) => {
  console.log(data, "选择的音频数据");
  closeedLoading.value = false;
  const res = await request.get(
    "/work_ai",
    `/user/shotstack/parseAudioToTxt/get`,
    {
      TaskId: data.id,
    }
  );

  if (res.result.Data.StatusStr !== "success") {
    // 继续轮训
    timerId.value = setTimeout(() => {
      initData(data);
      return;
    }, 5000);
  } else {
    if (dataSeparation.value.tts_config_audio.length < 5) {
      // 关闭loading 状态 这里是父元素 传一个状态值 给子元素
      closeedLoading.value = true;
      if (res.result.captions.length == 0) {
        message.warning("未识别到音频, 请重试!");
        audioDialog.value.closeLodingDialog();
        return;
      }

      const tts_data = baseTts_config();
      tts_data.subtitle = [];
      tts_data.iccts[0].elements = [];
      tts_data.tab_id = "audio";
      console.log(res.result, "音频的结果");

      // 基础的subtitle数据
      const sub = JSON.parse(
        JSON.stringify(dataSeparation.value.tts_config_audio[0].subtitle[0])
      );

      let importSubtitle = [];
      // 基础的字体大小
      const font_size = +sub.font_size / scaleData.value.scaleWidth;

      for (
        let sub_item = 0;
        sub_item < res.result.captions.captionsShow.length;
        sub_item++
      ) {
        const item = res.result.captions.captionsShow[sub_item];
        item.EndMs = item.EndMs * 1000;
        item.StartMs = item.StartMs * 1000;
        const textWidth = await getTextWidthUsingCanvas(
          item?.FinalSentence,
          font_size,
          sub.font_family
        );

        importSubtitle[sub_item] = {
          ...JSON.parse(JSON.stringify(sub)),
          text: item?.FinalSentence || "",
          ssml: "<speak>" + item?.FinalSentence + "</speak>",
          subtitle_id: nanoid(),
          x: sub.showX - textWidth / 2,
          y: sizeData.value.draggableHeight / subtitleHeightratio,
          material_path: "",
          audio_url: "",
          start_time: item.StartMs,
          end_time: item.EndMs,
          duration: item.EndMs - item.StartMs,
        };
      }

      console.log(
        importSubtitle,
        "importSubtitleimportSubtitleimportSubtitleimportSubtitle"
      );
      tts_data.subtitle = importSubtitle;
      tts_data.tab_id = "audio";
      tts_data.audio_url = data.url;
      tts_data.start_time = data.start_time;
      tts_data.end_time = data.end_time;
      tts_data.duration = tts_data.end_time - tts_data.start_time;
      tts_data.media_id = data?.media_id || "";
      tts_data.ssmlContent = importSubtitle
        .map(
          (ele) =>
            `<speak subId="${ele.subtitle_id}" tts_id="${tts_data.tts_id}">${ele.text}</speak>`
        )
        .join("");

      // 新增 音频使用次数 需求  --新增id
      const matchingMaterial = start_upload_Alldata.value.find(
        (item) => item.duration === data.duration
      );
      if (matchingMaterial) {
        tts_data.audio_material_id = matchingMaterial.id;
      }

      const audioArr = subTitle.value[
        currentDrawerIndex.value.index
      ].tts_config.filter((ele) => {
        return ele.tab_id == "audio";
      });

      // 只有确保音频项只有一个 且内部的字幕为空, 才替换第一项, 否则新增
      audioArr.length == 1 &&
        audioArr[0].subtitle.length == 1 &&
        audioArr[0].subtitle[0].text == ""
        ? (audioArr[0] = Object.assign(audioArr[0], tts_data))
        : subTitle.value[currentDrawerIndex.value.index].tts_config.push(
          tts_data
        );
      store.commit("videoMixCut/INIT_SUBTITLES_DATA", subTitle.value);
      console.log(
        subTitle.value[currentDrawerIndex.value.index],
        "音频天啊及之"
      );
      currentId.value = tts_data.tts_id;
      // 关闭音频分离的相关弹窗
      audioDialog.value.reset();
    } else {
      // 最多加5项
      message.warning("最多添加5个字幕!");
      audioDialog.value.closeLodingDialog();
    }
  }
};

// 删除音频数据
const del_upload_Alldata = (index) => {
  start_upload_Alldata.value.splice(index, 1);
};

// 是否展示audio
const showAudio = computed(() => {
  return dataSeparation.value.tts_config_audio.some(
    (ele) => ele.audio_url != ""
  );
  // return dataSeparation.value.tts_config_audio.some(ele => {
  //   return ele.subtitle.some(i => i.text != '' || i.audio_url != '')
  // })
});

// 所有的音频富文本实例
const TextEditing_audioRef = ref([]);
// 所有的手动设置字幕富文本实例
const TextEditing_terxtRef = ref([]);

// 打开文案库选择
const openCopyLibraryModal = (type = "open") => {
  if (type == "open") {
    copyLibraryModal.value.showModal();
  } else {
    copyLibraryModal.value.closeModal();
  }
};

// 文案库选择文案回调
const closeChooseMaterial = async (data) => {
  console.log(data, "选择的文案");
  const key = "material_content";
  const result = importListToRichtext_subtitle({
    data,
    key,
    sizeData,
    xLocation,
    dataSeparation,
    scaleData,
    subtitleHeightratio,
  });

  console.log(result, "镜头组处理完之后的数据");
  importNextStep(result);
};

// 导入文案之后的步骤
const importNextStep = (result) => {
  subTitle.value[currentDrawerIndex.value.index].tts_config = [
    ...result,
    ...dataSeparation.value.tts_config_audio,
  ];
  store.commit("videoMixCut/INIT_SUBTITLES_DATA", subTitle.value);
  nextTick(() => {
    // 更新富文本组件
    TextEditing_terxtRef.value.forEach((ele) => {
      ele.updateRichText();
    });
    nextTick(() => {
      // 修改当前展开的项
      foldManual(result[0].tts_id);
    });
  });
};

// 打开文案仿写弹窗
const openTextImitation = () => {
  TextImitationDialogRef.value.showModal();
};

// 获得文案仿写返回的数据
const getTextArr = (list) => {
  console.log(list, "传递过来的list");
  const result = importListToRichtext_subtitle({
    data: list,
    key: "content",
    sizeData,
    xLocation,
    dataSeparation,
    scaleData,
    subtitleHeightratio,
  });

  importNextStep(result);
  TextImitationDialogRef.value.closeModal();
};

// 控制遮罩层开关
const loadingFlage = ref(false)
// 遮罩文案
const loadingText = ref('音频获取中, 请耐心等待...')


// 字幕配置应用到全部
const applyallSubtitleFn = async () => {
  loadingText.value = '加载中...'
  loadingFlage.value = true
  try {

    const data = await applyallSubtitle({
        subTitle: subTitle,
        currentDrawerIndex: currentDrawerIndex,
        tab_id: tab_id,
      });

      store.dispatch("videoMixCut/SetVideoMashupItem", {
        key: "resource_data",
        value: data,
      });
  } catch (error) {

  } finally {
    setTimeout(() => {
      loadingFlage.value = false
    }, 1000)
  }

}

// 配音设置 应用到全部
const useConfigurationOverrideFn = async() => {
  loadingText.value = '加载中...'
  loadingFlage.value = true
  try {
    const data = await applyallVoice({
        subTitle: subTitle,
        currentDrawerIndex: currentDrawerIndex,
        tab_id: tab_id,
      });
      store.dispatch("videoMixCut/SetVideoMashupItem", {
        key: "resource_data",
        value: data,
      });
  } catch (error) {

  } finally {
    setTimeout(() => {
      loadingFlage.value = false
    }, 1000)
  }
}

// 暴露给父组件的方法
defineExpose({
  openDrawer,
  closeDrawer,
  getVoiceData,
});
</script>

<template>
  <div class="SubtitledubbingDrawer">
    <transition name="fade">
      <!-- :destroyOnClose="true" v-if="visible"-->
      <a-drawer v-model:visible="visible" :destroyOnClose="false" class="custom-class" 
        placement="right" :style="{
          'min-width': visible ? '420px' : 0,
        }" :bodyStyle="{
          paddingTop: 0,
          color: '#42464e',
        }" :closable="false" :maskClosable="false" :keyboard="false" width="50%">
        <slot name="title">
          <div class="title_box">
            <div class="title_top">
              <h1 class="title">添加字幕与配音-{{ title_top }}</h1>
              <!-- {{ editSubtitleItem.x + "x" }} -->
              <div class="close" @click="visible = false">
                <CloseOutlined />
              </div>
            </div>
            <div class="title_bottom">
              <a-button @click="prevGroup('last')" class="btn_prev" style="margin-right: 10px"
                :disabled="currentDrawerIndex.index == 0">上一个镜头组</a-button>
              <a-button @click="prevGroup('next')" class="btn_prev"
                :disabled="currentDrawerIndex.index == subTitle.length - 1">下一个镜头组</a-button>
              <!-- {{ editSubtitleItem.x + 'editSubtitleItem' }} -->
            </div>
          </div>
        </slot>
        <div class="content">
          <!-- 添加字幕标题 -->
          <div class="content_item">
            <!-- 算力消耗提示 -->
            <p v-if="tips" style="font-weight: bold; color: var(--ss-error-color-active);">
              <InfoCircleOutlined />
              {{tips}}
            </p>
            <div class="content_item_title">
              <h2>添加字幕内容</h2>
              <span>如果添加了多组字幕&配音，将被平均分配给镜头组合</span>
              <!-- {{ store.state.videoMixCut.VideoPlayingData + 'shuju asjkldfh ljkasjdf ' }} -->
            </div>
            <div class="switch">
              <div class="switch_box">
                <div class="switch_item" :class="{
                  activeSwitch: tab_id == 'text',
                }" @click="switchDisplay('text')">
                  手动设置字幕
                </div>
                <div class="switch_item" :class="{
                  activeSwitch: tab_id == 'audio',
                }" @click="switchDisplay('audio')">
                  音频生成字幕
                </div>
              </div>
              <div class="content_item_AI" v-if="tab_id == 'text'">
                <a-button size="small" @click="openCopyLibraryModal('open')" style="display: flex; align-items: center">
                  <cu-icon class="icon" type="icon-bendiwenanku"></cu-icon>
                  文案库选择
                </a-button>
                <a-button size="small" :loading="iconLoading" @click="openTextImitation"
                  style="display: flex; align-items: center">
                  <cu-icon class="icon" type="icon-kaishichuangzuo"></cu-icon>
                  文案仿写
                </a-button>
              </div>
            </div>

            <template v-if="visible">
            <!-- 音频生成字幕 -->
            <div v-show="tab_id == 'audio'">
              <!-- 素材库导入 -->
              <div class="upload_btn_box">
                <a-button type="primary" style="border-radius: 7px" @click="emit('openUpLoad')">
                  <UploadOutlined /> 素材库导入
                </a-button>
                <!-- 头部生成字幕选项 -->
                <div style="display: flex; align-items: center; width: 100%" v-for="item in start_upload_Alldata"
                  :key="item.id">
                  <div class="upload_one">
                    <div class="upload_one_left">
                      <FileDoneOutlined style="font-size: 16px" />
                      <div class="upload_one_left_tile">
                        {{ item.name }}
                      </div>
                    </div>
                    <div class="upload_one_right">
                      <span v-if="item.isOK == false" style="color: #0c0d0e">
                        上传中
                        <loadingOutlined />
                      </span>
                      <a-button v-else size="small" style="border-radius: 7px; padding: 0 12px" @click="toAudio(item)">
                        生成字幕
                      </a-button>
                    </div>
                  </div>
                  <a-popconfirm placement="topLeft" title="确认删除?" ok-text="确定" cancel-text="取消" trigger="click"
                    @confirm="del_upload_Alldata(index)">
                    <DeleteOutlined v-if="item.isOK == true" style="
                        font-size: 16px;
                        margin: 18px 0 0 5px;
                        cursor: pointer;
                      " />
                  </a-popconfirm>
                </div>
              </div>
              <!-- 富文本主体 -->
              <div v-show="tab_id == 'audio' && showAudio">
                <template v-for="(i, index) in dataSeparation.tts_config_audio" :key="i.tts_id">
                  <div v-show="currentId == i.tts_id">
                    <TextEditing importType="aliyun" :ref="(el) => (TextEditing_audioRef[index] = el)"
                      :tts_id="i.tts_id" :showIndex="index" :tab_id="i.tab_id">
                    </TextEditing>
                  </div>
                  <!-- <div v-show="currentId != i.tts_id">
                    <div class="fold_manual_box" @click="foldManual(i.tts_id)">
                      {{ "字幕" + (index + 1) }}
                    </div>
                  </div> -->
                  <!-- 折叠起来的样式 -->
                  <div v-show="currentId != i.tts_id" class="fold_manual_box" @click="foldManual(i.tts_id)">
                    <div class="fold_manual_title">
                      {{ "字幕" + (index + 1) }}
                    </div>
                    <div class="edit_show_msg" v-if="!!TextEditing_audioRef?.[index]">
                      <!-- 文本预计时长 -->
                      <div class="duration">
                        预计时长:
                        <span class="time_content">{{
                          TextEditing_audioRef[index].duration
                          }}</span>秒
                      </div>

                      <!-- 文本字数进度 -->
                      <div :class="{
                        'character-count': true,
                        'character-count--warning':
                          TextEditing_audioRef?.[index]?.text_num ===
                          TextEditing_audioRef?.[index]?.limit,
                      }">
                        <svg height="20" width="20" viewBox="0 0 20 20">
                          <circle r="10" cx="10" cy="10" fill="#e9ecef" />
                          <circle r="5" cx="10" cy="10" fill="transparent" stroke="currentColor" stroke-width="10"
                            :stroke-dasharray="`calc(${Math.round(
                              (100 / TextEditing_audioRef?.[index]?.limit) *
                              TextEditing_audioRef?.[index]?.text_num
                            )} * 31.4 / 100) 31.4`" transform="rotate(-90) translate(-20)" />
                          <circle r="6" cx="10" cy="10" fill="white" />
                        </svg>
                        {{ TextEditing_audioRef?.[index]?.text_num }} /
                        {{ TextEditing_audioRef?.[index]?.limit }}
                        <br />
                      </div>
                    </div>
                  </div>
                </template>
              </div>
            </div>

            <!-- 手动设置字幕 -->
            <div v-show="tab_id == 'text'">
              <template v-for="(i, index) in dataSeparation.tts_config_text" :key="i.tts_id">
                <div v-show="currentId == i.tts_id">
                  <TextEditing importType="aliyun" :ref="(el) => (TextEditing_terxtRef[index] = el)" :showIndex="index"
                    :tts_id="i.tts_id" :tab_id="i.tab_id">
                  </TextEditing>
                </div>
                <!-- 折叠起来的样式 -->
                <div v-show="currentId != i.tts_id" class="fold_manual_box" @click="foldManual(i.tts_id)">
                  <div class="fold_manual_title">
                    {{ "字幕" + (index + 1) }}
                  </div>
                  <div class="edit_show_msg" v-if="!!TextEditing_terxtRef?.[index]">
                    <!-- 文本预计时长 -->
                    <div class="duration">
                      预计时长:
                      <span class="time_content">{{
                        TextEditing_terxtRef[index].duration
                        }}</span>秒
                    </div>

                    <!-- 文本字数进度 -->
                    <div :class="{
                      'character-count': true,
                      'character-count--warning':
                        TextEditing_terxtRef?.[index]?.text_num ===
                        TextEditing_terxtRef?.[index]?.limit,
                    }">
                      <svg height="20" width="20" viewBox="0 0 20 20">
                        <circle r="10" cx="10" cy="10" fill="#e9ecef" />
                        <circle r="5" cx="10" cy="10" fill="transparent" stroke="currentColor" stroke-width="10"
                          :stroke-dasharray="`calc(${Math.round(
                            (100 / TextEditing_terxtRef?.[index]?.limit) *
                            TextEditing_terxtRef?.[index]?.text_num
                          )} * 31.4 / 100) 31.4`" transform="rotate(-90) translate(-20)" />
                        <circle r="6" cx="10" cy="10" fill="white" />
                      </svg>
                      {{ TextEditing_terxtRef?.[index]?.text_num }} /
                      {{ TextEditing_terxtRef?.[index]?.limit }}
                      <br />
                    </div>
                  </div>
                </div>
              </template>
              <!-- 添加字幕 -->
              <a-button class="add_subtitle_btn" type="dashed" @click="addeditorArr" ghost>
                <PlusOutlined />添加字幕
              </a-button>
            </div>
            </template>


            <!-- 添加字幕标题 -->
            <div class="content_item" style="margin-top: 40px">
              <div class="content_item_title">
                <h2>视频设置</h2>
                <!-- {{ parentBgc.background + 'background' }} -->

                <a-button style="font-size: 13px" @click="addVideoGroupHandle">视频字幕设置应用到全部镜头组</a-button>
                <!-- {{ editSubtitleItem.x }} -->
              </div>
              <!-- 花字 and 配音组件 -->
              <SubtitlesFontStyleComponent ref="Subtitles_FontStyleComponent" @configurationOverride="configurationOverride"> </SubtitlesFontStyleComponent>

            </div>
          </div>

          <!-- 手机组件 -->
          <div v-if="visible" id="phoneConCover" class="phoneConCover_content" :style="{
            opacity: phoneVisible ? 1 : 0,
            transition: 'opacity 0.5s',
            left: visible ? 'calc((100% - 50%) / 2)' : '-999999px',
            width: 360 + 30 + 'px',
            height: 730 + 47.809 + 'px'
          }">

            <!-- 手机头部 -->
            <div class="mobile-header">
              <div class="time">{{ dayjs().format("HH:mm") }}</div>
              <div class="wife">
                <cu-icon type="icon-xinhao" style="font-size: 12px"></cu-icon>
                <cu-icon type="icon-wife" style="margin: 0 2px; font-size: 14px"></cu-icon>
                <cu-icon type="icon-electricity-full" style="font-size: 14px"></cu-icon>
              </div>
            </div>
            <!-- 模拟抖音背景 -->
            <div class="bgc_content" :style="{
              'background-image': showImg
                ? `url(${utils.staticPath + 'images/workAi/shotstack/bg_cover.png'
                })`
                : '',
            }"></div>

            <!-- 素材背景图 -->
            <div class="bgc_content" :style="{
              ...parentBgc,
              'z-index': 1,
              left: 0
            }">
            </div>
            <!-- 底层背景图 -->
            <div class="left_phone_view" :style="{
              ...bgc,
              display: 'flex',
              'justify-content': 'center',
              'align-items': 'center'
            }">
              <!-- <a-spin style="width: 100%; height: 640px" :spinning="loading"> -->
              <DraggableContainer :style="resizableStyle" :referenceLineColor="'white'">
                <Vue3DraggableResizable style="padding: 0; z-index: 3;" v-model:x="editSubtitleItem.x"
                  v-model:y="editSubtitleItem.y" v-model:w="ResizableWidth" v-model:h="Resizableheight"
                  v-model:active="ResizableActive" :lockAspectRatio="true" :resizable="false" :draggable="true"
                  :parent="true" @drag-end="dragEndHandle" :key="editSubtitleItem.subtitle_id + editSubtitleItem.text">
                  <p :style="{ ...coverStyle() }" class="editor_content">
                    {{ editSubtitleItem.text }}
                  </p>
                </Vue3DraggableResizable>

                <p :style="{ ...coverStyle(), opacity: 0 }" id="editor_content_p" class="editor_content">
                  {{ editSubtitleItem.text }}
                </p>
              </DraggableContainer>
            </div>
            <div class="bottom_View_control">
              <a-button @click="showImg = !showImg">{{ showImg ? "关闭" : "开启" }}抖音视图</a-button>
            </div>

          </div>
        </div>
        <template #footer>
          <div class="bottom_btn">
            <a-button style="margin-right: 15px" @click="close">取消</a-button>
            <a-button type="primary" @click="submitConfirm" :loading="submitLoading">确定</a-button>
          </div>
        </template>
      </a-drawer>
    </transition>
    <!-- 查看音频 -->
    <ViewAudioModel ref="audioDialog" :start_upload_data="start_upload_data" :closeedLoading="closeedLoading"
      @update="update" @cancelLoding="cancelLoding" @audioLoading="audioLoading" @ReAdd="emit('openUpLoad', 'replay')">
    </ViewAudioModel>

    <!-- 文案库 -->
    <CopyLibraryModal ref="copyLibraryModal" selectType="checkbox" @importSuccess="closeChooseMaterial" />

    <!-- 文案仿写组件 -->
    <TextImitationDialog ref="TextImitationDialogRef" :isComponents="true" @getTextArr="getTextArr">
    </TextImitationDialog>

    <!-- 预览自定义音色的音频节点 -->
    <audio @ended="handleGlobalAudioEnded" ref="globalAudio" :src="playingItem" style="display: none"></audio>
  </div>

  <!-- 充值弹窗 -->
  <vipModal ref="vipModalRef" :visible="vipVisible" @close="vipVisible = false"></vipModal>

  <!-- loading 遮罩 -->
  <loadingMask ref="loadingMaskRef" :text="loadingText" :zIndex="1001" :loading="loadingFlage"></loadingMask>
</template>

<style scoped lang="less">
// 切换动画

.SubtitledubbingDrawer {}

:deep(.ant-spin-container) {
  background-color: #131313;
  overflow: hidden;
}

// 头部样式
.title_box {
  width: 100%;
  padding-bottom: 10px;
  padding-top: 24px;
  position: sticky;
  top: 0;
  background-color: #fff;
  z-index: 999;

  &::after {
    content: "";
    height: 1px;
    width: calc(100% + 48px);
    background-color: #e8e8e8;
    position: absolute;
    bottom: 0;
    left: -24px;
  }

  .title_top {
    display: flex;
    justify-content: space-between;
    color: #0c0d0e;

    // margin-bottom: 10px;
    h1 {
      font-size: 16px;
      font-weight: 600;
      margin-bottom: 4px;
    }

    .close {
      cursor: pointer;
      text-align: center;
      line-height: 29px;
      padding: 0 6px;

      &:hover {
        background-color: #f3f3f4;
      }
    }
  }

  .title_bottom {
    .btn_prev {
      border-radius: 5px;
      padding: 0 16px;
      font-size: 12px;
      height: 28px;
    }
  }
}

// 整体样式
.content {
  padding-top: 20px;
  position: relative;

  // 手机样式
  .phoneConCover_content {
    // width: 360px;
    // height: 730px;
    position: fixed;
    border-radius: 20px;
    top: 50%;
    left: calc(calc(100% - 50%) / 2);
    transform: translate(-50%, -50%);
    background-color: #000;
    display: flex;
    // flex-direction: column;
    align-items: center;
    justify-content: center;
    // overflow: hidden;

    .mobile-header {
      height: 44px;
      width: 100%;
      position: absolute;
      left: 0;
      top: 0;
      border-top-left-radius: 20px;
      border-top-right-radius: 20px;
      border-bottom: 1px solid rgba(255, 255, 255, 0.281);
      background: black;
      display: flex;
      align-items: center;
      justify-content: space-between;
      color: #fff;
      padding: 10px 10px;
      overflow: hidden;
    }

    // 背景图
    .bgc_content {
      position: absolute;
      top: 43.5px;
      left: 0;
      width: 100%;
      height: calc(100% - 88px);
      background-repeat: no-repeat;
      background-size: contain;
      // background-size: 100%;
      // height: 100%;
      /* 添加这一行 */
      pointer-events: none;
      z-index: 2;
    }

    .left_phone_view {
      overflow: hidden;
      position: relative;
      width: 100%;
      height: calc(100% - 88px);
      display: flex;
      align-items: center;
      justify-content: center;
      border-bottom: 1px solid rgba(255, 255, 255, 0.281);

      .editor_content {
        margin-bottom: 0;
        border: none;
        resize: none;
        height: auto;
        display: inline-block;
        // overflow: hidden;
        // 禁止选中
        pointer-events: none;
        // 换行显示
        white-space: pre-wrap;
        // 不考虑连贯性, 强制换行
        word-break: break-all;
      }
    }

    // 手机下方的控制按钮
    .bottom_View_control {
      position: absolute;
      bottom: -50px;
      left: 50%;
      z-index: 5;
      transform: translate(-50%, 0);
      display: flex;
    }
  }

  .content_item {

    // 每一项富文本折起来的样式
    .fold_manual_box {
      width: 100%;
      line-height: 33px;
      background-color: #f6f8fa;
      padding: 1px 15px;
      cursor: pointer;
      border-radius: 5px;
      margin-top: 10px;
      font-size: 12px;
      color: #737a87;
      display: flex;
      align-items: center;
      // justify-content: space-between;
      gap: 0 15px;
      border: 1px solid transparent;
      transition: all 0.3s;

      &:hover {
        border-color: var(--ss-primary-color-hover);
      }

      // 折叠起来的样式
      .fold_manual_title {}

      .edit_show_msg {
        display: flex;
        align-items: center;
        gap: 10px;

        .duration {
          color: #737a87;
        }

        // 文本上限提示
        .character-count {
          align-items: center;
          color: var(--ss-primary-5);
          display: flex;
          font-size: 0.75rem;
          gap: 0.5rem;

          svg {
            color: var(--ss-primary-5);
          }

          &--warning,
          &--warning svg {
            color: red;
          }
        }
      }
    }

    .upload_btn_box {
      margin-top: 20px;

      .upload_one {
        width: 97%;
        background-color: #f5f7f9;
        margin-top: 20px;
        padding: 6px 12px;
        display: flex;
        justify-content: space-between;

        .upload_one_left {
          width: 85%;
          display: flex;
          align-items: center;
          justify-content: space-between;
        }

        .upload_one_left_tile {
          width: 96%;
          overflow: hidden;
          white-space: nowrap;
          text-overflow: ellipsis;
          color: #0c0d0e;
        }
      }
    }

    .content_item_title {
      display: flex;
      justify-content: space-between;
      align-items: center;
      margin-bottom: 15px;

      h2 {
        font-size: 13px;
        font-weight: 600;
        color: #1e1c23;
        margin-bottom: 0;
      }

      span {
        font-size: 12px;
        color: #737a87;
      }
    }

    // 选择字幕内容生成方式
    // 选择字幕内容生成方式
    .switch {
      margin-top: 10px;
      display: flex;
      justify-content: space-between;

      .switch_box {
        width: 213px;
        padding: 3px;
        background-color: #f1f3f5;
        display: flex;
        border-radius: 3px;
        overflow: hidden;
        // margin-top: 6px;

        .switch_item {
          line-height: 28px;
          flex: 1;
          font-size: 13px;
          color: #42464e;
          border-radius: 3px;
          overflow: hidden;
          text-align: center;
          display: flex;
          justify-content: center;
          align-items: center;
          cursor: pointer;

          &:hover {
            color: #3261fb;
          }
        }

        // .switch_AI {
        //   :deep(.ant-btn) {
        //     span {
        //       height: 100%;
        //       line-height: normal;
        //     }
        //   }
        // }
        .activeSwitch {
          background-color: #fff;
          color: #3261fb;
        }
      }

      .content_item_AI {
        display: flex;
        gap: 10px;

        .icon {
          display: flex;
          align-items: center;
          color: #2580fd;
          font-size: 18px;
        }
      }
    }

    // 手动设置字幕 样式
    .manual_box {
      background-color: #f6f8fa;
      padding: 15px;
      margin-top: 18px;
      border-radius: 5px;

      // 编辑容器样式
      .editor_container {
        // min-height: 150px;
        background-color: #fff;
        border-radius: 8px;
        position: relative;
        padding: 7px 20px;
        padding-bottom: 35px;

        .editor_content_box {
          // padding: 8px 52px 30px 28px;
          display: flex;
          flex-direction: column;

          .editor_content_item {
            display: flex;
            flex-direction: column;
            position: relative;

            .editor_content_iatem_box {
              position: relative;
              display: flex;

              .editor_content_ele_point {
                cursor: pointer;
                color: #c7ccd6;
                position: absolute;
                left: -14px;
                top: 0;
              }

              .editor_content {
                outline: none;
                color: #0c0d0e;
                margin-bottom: 0;
                padding-left: 3px;
                padding-right: 2px;
                border: none;
                resize: none;
                height: auto;
                min-height: 24px;
                // display: inline-block;
              }
            }
          }
        }

        // 每一项 底部的操作按钮容器
        .editor_operation {
          display: flex;
          position: absolute;
          bottom: 5px;
          left: 5px;
          overflow: hidden;

          // 每一项 正常的状态
          .editor_operation_item {
            min-width: 78px;
            display: flex;
            align-items: center;
            gap: 2px;
            margin-right: 6px;
            padding: 2px 8px;
            background-color: #f4f5f5;
            border-radius: 3px;
            overflow: hidden;
            cursor: pointer;
            font-size: 12px;
            color: #1c1f23b3;
            // 静止选取文字
            -webkit-user-select: none;
            /* Safari */
            -moz-user-select: none;
            /* Firefox */
            -ms-user-select: none;
            /* Internet Explorer/Edge */
            user-select: none;

            /* 非前缀版本，适用于Chrome和Opera */
            &:hover {
              background-color: #eceded;
            }
          }

          // 禁用的状态
          .disable_editor_operation_item {
            cursor: not-allowed;
            background-color: #f9fafa;
            color: #aeafb0;

            &:hover {
              background-color: #f9fafa;
              color: #aeafb0;
            }
          }
        }
      }

      // 标题样式
      .manual_title {
        display: flex;
        justify-content: space-between;
        align-items: center;
        margin-bottom: 10px;

        .title_text {
          font-size: 14px;
          color: #0c0d0e;
          font-weight: 600;
        }

        .operation {
          display: flex;
          align-items: center;
          gap: 10px;

          .delete_btn {
            background-color: #fff;
            border: 1px solid #dde2e9;
            font-size: 13px;
            color: #42464e;
            border-radius: 3px;
            padding: 0px 7px;
            cursor: pointer;

            &:hover {
              border-color: #3261fb;
            }
          }

          .disable_delete_btn {
            cursor: not-allowed;
            border-color: #dde2e9;
            color: #c7ccd6;

            &:hover {
              cursor: not-allowed;
              border-color: #dde2e9;
              color: #c7ccd6;
            }
          }
        }
      }

      .manual_audio {
        width: 100%;
        height: 86px;
        background-color: #fff;
        margin-bottom: 20px;
        padding: 14px;
        display: flex;

        .video_box_left_one {
          width: 50px;
          height: 50px;
          background-color: #bec0c2;
          border-radius: 3px;
          text-align: center;
          line-height: 56px;
          margin-right: 20px;
        }

        .manual_audio_right {
          color: #000;
          flex: 1;

          .manual_audio_right_top {
            width: 100%;
            overflow: hidden;
            white-space: nowrap;
            text-overflow: ellipsis;
            font-size: 14px;
            font-weight: 600;
            color: #000;
            margin-bottom: 5px;
          }
        }
      }
    }

    // 添加按钮
    .add_subtitle_btn {
      width: 100%;
      background-color: #fafbfc;
      border-color: #dde2e9;
      color: #42464e;
      margin-top: 10px;

      &:hover {
        border-color: #3261fb;
      }
    }
  }
}

// 底部按钮
.bottom_btn {
  padding: 8px 24px;
  display: flex;
  justify-content: flex-end;
  background-color: #fff;
}
</style>
